package com.example.exam.service.impl;

import com.example.exam.pojo.DTO.QuestionDTO.QuestionEditDTO;
import com.example.exam.pojo.DTO.QuestionDTO.QuestionObject;
import com.example.exam.pojo.Enum.QuestionTypeEnum;
import com.example.exam.pojo.Exception.ServiceException;
import com.example.exam.mapper.TQuestionMapper;
import com.example.exam.mapper.TTextContentMapper;
import com.example.exam.pojo.entity.TQuestion;
import com.example.exam.pojo.entity.TTextContent;
import com.example.exam.pojo.vo.QuestionVO.QuestionContentVO;
import com.example.exam.pojo.vo.QuestionVO.QuestionEditItemVO;
import com.example.exam.pojo.vo.QuestionVO.QuestionStandardVO;
import com.example.exam.pojo.vo.TextContentVO.TextContentStandardVO;
import com.example.exam.service.IQuestionService;
import com.example.exam.service.ITextContentService;
import com.example.exam.tools.*;
import com.github.pagehelper.PageHelper;
import com.github.pagehelper.PageInfo;
import lombok.extern.slf4j.Slf4j;
import org.apache.tomcat.util.buf.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.Arrays;
import java.util.List;
import java.util.stream.Collectors;

@Transactional
@Service
@Slf4j
public class QuestionServiceImpl extends BaseApiController implements IQuestionService {

    @Autowired
    private TQuestionMapper questionMapper;
    @Autowired
    private TTextContentMapper textContentMapper;
    @Autowired
    private ITextContentService textContentService;

    /**
     * 题目映射
     * @param id
     * @return
     */
    @Override
    public QuestionEditDTO getQuestionEditDTO(Integer id) {

        TQuestion question = questionMapper.selectById(id);
        return getQuestionEditDTO(question);
    }

    public QuestionEditDTO getQuestionEditDTO(TQuestion question){
        //题目映射
        TTextContent textContent = textContentService.selectById(question.getId());
        QuestionObject questionObject = JsonUtil.toJsonObject(textContent.getContent(),QuestionObject.class);
        QuestionEditDTO questionDTO = modelMapper.map(question, QuestionEditDTO.class);
        questionDTO.setTitle(questionObject.getTitleContent());

        //答案
        QuestionTypeEnum questionTypeEnum = QuestionTypeEnum.fromCode(question.getQuestionType());
        switch (questionTypeEnum){
            case SingleChoice:
            case TrueFalse:
                questionDTO.setCorrect(question.getCorrect());
                break;
            case MultipleChoice:
                questionDTO.setCorrectArray(ExamUtil.contentToArray(question.getCorrect()));
                break;
            case GapFilling:
                List<String> correctContent = questionObject.getQuestionItemObjects().stream()
                        .map(d -> d.getContent()).collect(Collectors.toList());
                questionDTO.setCorrectArray(correctContent);
                break;
            case ShortAnswer:
                questionDTO.setCorrect(questionObject.getCorrect());
                break;
            default:
                break;
        }

        questionDTO.setScore(ExamUtil.scoreToVM(question.getScore()));
        questionDTO.setAnalyze(questionObject.getAnalyze());

        //题目项映射
        List<QuestionEditItemVO> items = questionObject.getQuestionItemObjects().stream().map(o -> {
            QuestionEditItemVO itemVO = modelMapper.map(o, QuestionEditItemVO.class);
            if (o.getScore() != null) {
                itemVO.setScore(o.getScore());
            }
            return itemVO;
        }).collect(Collectors.toList());
        questionDTO.setItems(items);
        return questionDTO;
    }

    @Override
    public JsonPage<QuestionStandardVO> getQuestionByPage(QuestionStandardVO questionStandardVO) {
        log.debug("开始处理【分页查询题目列表】的业务，参数：{}", questionStandardVO);
        PageHelper.startPage(questionStandardVO.getPageIndex(), questionStandardVO.getPageSize());
        List<QuestionStandardVO> listByPage = questionMapper.findQuestions(questionStandardVO);
        JsonPage<QuestionStandardVO> questionStandardVOJsonPage = JsonPage.restPage(new PageInfo<>(listByPage));
        //把content里的内容转成对象，存入列表
        listByPage=questionStandardVOJsonPage.getList().stream().map(t->{
            QuestionStandardVO vo = JsonUtil.toJsonObject(t.getContent(), QuestionStandardVO.class);
            t.setTitleContent(vo.getTitleContent());
            return t;
        }).collect(Collectors.toList());
        questionStandardVOJsonPage.setList(listByPage);
        return questionStandardVOJsonPage;
    }

    @Override
    public String edit(QuestionStandardVO questionStandardVO) {
        log.debug("开始处理【添加或更新题目】的业务");
        QuestionContentVO questionContentVO=new QuestionContentVO();
        questionContentVO.setQuestionItemObjects(questionStandardVO.getQuestionItemObjects());
        questionContentVO.setTitleContent(questionStandardVO.getTitleContent());
        String content = JsonUtil.toJsonStr(questionContentVO);
        //将数组以逗号拼接成新的字符串
        if(questionStandardVO.getQuestionType()==2){
            questionStandardVO.setCorrect(StringUtils.join(questionStandardVO.getCorrectArray(), ','));
        }
        int row1=0;
        int row2=0;
        String response;
        if(questionStandardVO.getId()==null){
            if(textContentMapper.countByContent(content)==0){
                //向t_text_content表中插入数据
                log.debug("即将向数据库中插入数据：{}", content);
                row1=textContentMapper.insert(content);
            }
            int id = textContentMapper.getIdByContent(content);
            questionStandardVO.setInfoTextContentId(id);
            row1=1;

            //向t_question表中插入数据
            log.debug("即将向数据库中插入数据");
            questionStandardVO.setDeleted(false);
            questionStandardVO.setCreateUser(2);
            questionStandardVO.setStatus(1);
            row2= questionMapper.insert(questionStandardVO);
            response="添加题目成功";
        }
        else{
            //若没有内容相同的题目则修改
            if(textContentMapper.countByContent(content)==0){
                //向t_text_content表中更新数据
                log.debug("即将向数据库中更新数据：{}", content);
                TextContentStandardVO textContentStandardVO=new TextContentStandardVO();
                textContentStandardVO.setId(questionStandardVO.getInfoTextContentId());
                textContentStandardVO.setContent(content);
                row1=textContentMapper.update(textContentStandardVO);
            }
            else{
                int id=textContentMapper.getIdByContent(content);
                questionStandardVO.setInfoTextContentId(id);
                row1=1;
            }

            //向t_text_content表中更新数据
            log.debug("即将向数据库中更新数据");
            row2= questionMapper.update(questionStandardVO);
            response="修改题目成功";
        }

        if ((row1 != 1) || (row2 != 1)) {
            String message = "编辑题目失败！服务器忙，请稍后再尝试！";
            log.warn(message);
            throw new ServiceException(ServiceCode.ERR_INSERT, message);
        }
        return response;
    }

    @Override
    public void delete(Integer id) {
        log.debug("开始处理【删除题目】的业务,参数：{}", id);
        int row = questionMapper.deleteById(id);
        if (row <= 0) {
            String message = "删除题目失败！";
            log.warn(message);
            throw new ServiceException(ServiceCode.ERR_DELETE, message);
        }
    }

    @Override
    public QuestionStandardVO getStandardById(Integer id) {
        log.debug("开始处理【根据id查询题目】的业务,参数：{}", id);
        QuestionStandardVO standardById = questionMapper.getStandardById(id);
        //若题目正确答案为多选，那么把这些选项用逗号分隔
        if(standardById.getQuestionType()==2){
            standardById.setCorrectArray(Arrays.asList(standardById.getCorrect().split(",")));
        }
        //把表的content一栏转成jsonObject格式
        QuestionContentVO questionContentVO = JsonUtil.toJsonObject(standardById.getContent(), QuestionContentVO.class);
        //获取题目的选项
        standardById.setQuestionItemObjects(questionContentVO.getQuestionItemObjects());
        //获取题目的题干
        standardById.setTitleContent(questionContentVO.getTitleContent());
        return standardById;
    }

}
